/*#include "StdAfx.h"*/

#include "FileExecutor.h"

namespace Utility
{
    namespace LoggerLib
    {
        CFileExecutor::CFileExecutor(const wstring& strName) : IExecutor(strName),
            m_hFile(INVALID_HANDLE_VALUE),
            m_strFilePath(L"DefaultLog")
        {
            ZeroMemory(&m_stFileTime, sizeof(SYSTEMTIME));
            SetFilePath(m_strFilePath);
        }

        CFileExecutor::~CFileExecutor(void)
        {
            Close();
        }

        bool CFileExecutor::Reopen()
        {
            Close();
            return OpenFile();
        }

        void CFileExecutor::Close()
        {
            AUTO_LOCK(m_lockFile);

            if(m_hFile != INVALID_HANDLE_VALUE)
            {
                CloseHandle(m_hFile);
                m_hFile = INVALID_HANDLE_VALUE;
            }
        }

        bool CFileExecutor::DoLogging(const LoggingEvent& event)
        {
            AUTO_LOCK(m_lockFile);
            if(m_hFile == INVALID_HANDLE_VALUE)
            {
                if(!OpenFile())
                {
                    return false; 
                }
            }

            wstring strMsg = event.Format();
            int nSize = sizeof(TCHAR) * strMsg.length();
            DWORD dwPos = ::SetFilePointer(m_hFile, 0, NULL, FILE_END);
            DWORD dwLen = 0;
            LockFile(m_hFile, dwPos, 0, nSize, 0);
            BOOL bWriteFile = ::WriteFile(m_hFile, strMsg.c_str(), nSize, &dwLen, NULL);
            if(!bWriteFile)
            {
                // write file error
                UnlockFile(m_hFile, dwPos, 0, nSize, 0);
                return false;				
            }

            bWriteFile = WriteFile(m_hFile, L"\r\n", 2*sizeof(TCHAR), &dwLen, NULL);
            UnlockFile(m_hFile, dwPos, 0, nSize, 0);

            return bWriteFile? true:false;
        }

        void CFileExecutor::SetFilePath(const wstring& strPath)
        {
            AUTO_LOCK(m_lockFilePath);
            UpdateDate();

            wstring strTemp;
            if(strPath.empty())
            {
                strTemp = L"DefaultLog";
            }
            else
            {
                strTemp = strPath;
            }

            TCHAR tszPath[MAX_PATH] = {0};
            _snwprintf_s(tszPath, MAX_PATH, _TRUNCATE, (L"%s_%04d%02d%02d.log"), strTemp.c_str(), m_stFileTime.wYear,m_stFileTime.wMonth,m_stFileTime.wDay);
            m_strFilePath = tszPath;
        }

        void CFileExecutor::UpdateDate()
        {	
            SYSTEMTIME st;
            GetLocalTime(&st);
            if ((st.wYear!=m_stFileTime.wYear) || (st.wMonth!=m_stFileTime.wMonth) || (st.wDay!=m_stFileTime.wDay))
            {
                m_stFileTime.wYear = st.wYear;
                m_stFileTime.wMonth = st.wMonth;
                m_stFileTime.wDay = st.wDay;
            }
        }

        bool CFileExecutor::OpenFile()
        {		
            AUTO_LOCK(m_lockFile);
            if(m_hFile != INVALID_HANDLE_VALUE)
            {
                Close();
            }

            m_hFile = ::CreateFile(m_strFilePath.c_str(), GENERIC_WRITE, FILE_SHARE_READ, NULL, 
                OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); 
            if (m_hFile == INVALID_HANDLE_VALUE)
            {
                return false;
            }

            return true;
        }
    } // Logger
}